Escola de Métodos em Ciências Sociais
O tidyverse, também chamado por muitos de hadleyverse, é um conjunto de pacotes que, por compartilharem esses princípios do manifesto tidy, podem ser utilizados naturalmente em conjunto. Pode-se dizer que existe o R antes do tidyverse e o R depois do tidyverse.
Os princípios fundamentais do tidyverse são:
Reutilizar estruturas de dados existentes.
Organizar funções simples usando o pipe.
Aderir à programação funcional.
Projetado para ser usado por seres humanos.
Tidy Tools Manifesto https://cran.r-project.org/web/packages/tidyverse/vignettes/manifesto.html
Tidy data vignette https://cran.r-project.org/web/packages/tidyr/vignettes/tidy-data.html
Tidy Data paper http://vita.had.co.nz/papers/tidy-data.pdf
Conjunto de pacotes https://www.tidyverse.org/packages/
O operador %>% (pipe), depois |> foi uma das grandes revoluções recentes do R, tornando a leitura de códigos mais lógica, fácil e compreensível.
A ideia é bem simples: usar o valor resultante da expressão do lado esquerdo como primeiro argumento da função do lado direito.
Vamos calcular a raiz quadrada da soma dos valores de 1 a 4.
Primeiro, sem o pipe.
Agora com o pipe.
A utilização do pipe transforma um código confuso e difícil de ser lido em algo simples e intuitivo.
Tente entender o que é preciso fazer.
Desistiu? Agora veja como fica escrevendo com o %>%:
readr, readxl, haven e DBINo tidyverse, geralmente
read_<formato> servem para ler um arquivo no formato <formato>write_<formato> servem para escrever num arquivo com o formato <formato>csv, tsv, txt, …
Para esses aqui, usar o pacote readr
Você também pode experimentar o data.table::fread
baserm?Olha como ficou mais fácil agora:
library(readr)
baserm <- read_delim("dados/baserm.txt",
delim = "\t", escape_double = FALSE,
locale = locale(encoding = "WINDOWS-1252"),
trim_ws = TRUE)
baserm# A tibble: 27 × 168
sigla cod.ibge estado anoeleitoral1990 anoeleitoral1991 anoeleitoral1992
<dbl> <chr> <dbl> <chr> <dbl> <dbl>
1 1 AC 12 Acre 1 0
2 2 AL 27 Alagoas 1 0
3 3 AM 13 Amazonas 1 0
4 4 AP 16 Amapá 1 0
5 5 BA 29 Bahia 1 0
6 6 CE 23 Ceará 1 0
7 7 DF 53 Distrito Federal 1 0
8 8 ES 32 Espírito Santo 1 0
9 9 GO 52 Goiás 1 0
10 10 MA 21 Maranhão 1 0
# ℹ 17 more rows
# ℹ 162 more variables: anoeleitoral1993 <dbl>, anoeleitoral1994 <dbl>,
# anoeleitoral1995 <dbl>, anoeleitoral1996 <dbl>, anoeleitoral1997 <dbl>,
# anoeleitoral1998 <dbl>, anoeleitoral1999 <dbl>, anoeleitoral2000 <dbl>,
# anoeleitoral2001 <dbl>, anoeleitoral2002 <dbl>, anoeleitoral2003 <dbl>,
# anoeleitoral2004 <dbl>, anoeleitoral2005 <dbl>, anoeleitoral2006 <dbl>,
# anoeleitoral2007 <dbl>, anoeleitoral2008 <dbl>, anoeleitoral2009 <dbl>, …
.RData, .rds, .feather, .fst
.dta (Stata), .sas7bdat (SAS), .sav (SPSS)
Ler com readr, haven, feather, fst.
MySQL, SQL Server, PostgreSQL, SQLite, …
Spark, MongoDB, Hive, …
Utilizar pacotes DBI e odbc
dplyr e tidyrVamos trabalhar com a base decisoes, que contém decisões do Tribunal de Justiça de São Paulo
Rows: 11,731
Columns: 9
$ `ID Decisão` <chr> "11094999", "11093733", "11093677", "11093270", "1109…
$ n_processo <chr> "0057003-20.2017.8.26.0000", "0052762-03.2017.8.26.00…
$ `Classe/Assunto` <chr> "Habeas Corpus / Homicídio Simples", "Habeas Corpus /…
$ Município <chr> "Cosmópolis", "São Paulo", "Ribeirão Preto", "Araçatu…
$ Câmara <chr> "3ª Câmara de Direito Criminal", "3ª Câmara de Direit…
$ `Data decisão` <chr> "19/12/2017", "19/12/2017", "19/12/2017", "14/12/2017…
$ `Data registro` <chr> "19/12/2017", "19/12/2017", "19/12/2017", "19/12/2017…
$ Juiz <chr> "Luiz Antonio Cardoso", "Luiz Antonio Cardoso", "Luiz…
$ `txt decisão` <chr> NA, NA, NA, "Execução Penal – Comutação de Penas – …
library(janitor)
decisoes <- read_rds("dados/decisoes.rds") %>%
janitor::clean_names() # com dois pontos eu não preciso usar library
glimpse(decisoes)Rows: 11,731
Columns: 9
$ id_decisao <chr> "11094999", "11093733", "11093677", "11093270", "110933…
$ n_processo <chr> "0057003-20.2017.8.26.0000", "0052762-03.2017.8.26.0000…
$ classe_assunto <chr> "Habeas Corpus / Homicídio Simples", "Habeas Corpus / R…
$ municipio <chr> "Cosmópolis", "São Paulo", "Ribeirão Preto", "Araçatuba…
$ camara <chr> "3ª Câmara de Direito Criminal", "3ª Câmara de Direito …
$ data_decisao <chr> "19/12/2017", "19/12/2017", "19/12/2017", "14/12/2017",…
$ data_registro <chr> "19/12/2017", "19/12/2017", "19/12/2017", "19/12/2017",…
$ juiz <chr> "Luiz Antonio Cardoso", "Luiz Antonio Cardoso", "Luiz A…
$ txt_decisao <chr> NA, NA, NA, "Execução Penal – Comutação de Penas – De…
dplyrA utilização é facilitada com o emprego do operador %>%
No primeiro argumento colocamos o data.frame ou o tibble, e nos outros argumentos colocamos o que queremos fazer.
dplyrselect: selecionar colunas
filter: filtrar linhas
mutate: criar colunas
summarise: sumarizar colunas
arrange: ordenar linhas
selectstarts_with(x), contains(x), matches(x), one_of(x), etc.:.select em ação 1# A tibble: 11,731 × 4
id_decisao n_processo municipio juiz
<chr> <chr> <chr> <chr>
1 11094999 0057003-20.2017.8.26.0000 Cosmópolis Luiz Antonio Cardoso
2 11093733 0052762-03.2017.8.26.0000 São Paulo Luiz Antonio Cardoso
3 11093677 0055169-79.2017.8.26.0000 Ribeirão Preto Luiz Antonio Cardoso
4 11093270 9000580-82.2017.8.26.0032 Araçatuba Grassi Neto
5 11093374 0052938-79.2017.8.26.0000 São Paulo Grassi Neto
6 11093320 9000723-79.2017.8.26.0482 Presidente Prudente Grassi Neto
7 11091506 0003276-86.2015.8.26.0075 Bertioga Grassi Neto
8 11093326 9000298-11.2017.8.26.0625 Taubaté Grassi Neto
9 11092475 0004653-39.2015.8.26.0028 Aparecida Grassi Neto
10 11093773 2221930-66.2017.8.26.0000 Jandira Luiz Antonio Cardoso
# ℹ 11,721 more rows
select em ação 2# A tibble: 11,731 × 4
classe_assunto n_processo id_decisao juiz
<chr> <chr> <chr> <chr>
1 Habeas Corpus / Homicídio Simples 0057003-2… 11094999 Luiz…
2 Habeas Corpus / Roubo 0052762-0… 11093733 Luiz…
3 Habeas Corpus / DIREITO PENAL 0055169-7… 11093677 Luiz…
4 Agravo de Execução Penal / Pena Privativa de Lib… 9000580-8… 11093270 Gras…
5 Mandado de Segurança / Crimes do Sistema Naciona… 0052938-7… 11093374 Gras…
6 Agravo de Execução Penal / Pena Privativa de Lib… 9000723-7… 11093320 Gras…
7 Apelação / Tráfico de Drogas e Condutas Afins 0003276-8… 11091506 Gras…
8 Agravo de Execução Penal / Livramento Condicional 9000298-1… 11093326 Gras…
9 Apelação / Tráfico de Drogas e Condutas Afins 0004653-3… 11092475 Gras…
10 Habeas Corpus / Furto Qualificado 2221930-6… 11093773 Luiz…
# ℹ 11,721 more rows
select em ação 3# A tibble: 11,731 × 3
id_decisao data_decisao data_registro
<chr> <chr> <chr>
1 11094999 19/12/2017 19/12/2017
2 11093733 19/12/2017 19/12/2017
3 11093677 19/12/2017 19/12/2017
4 11093270 14/12/2017 19/12/2017
5 11093374 14/12/2017 19/12/2017
6 11093320 14/12/2017 19/12/2017
7 11091506 14/12/2017 19/12/2017
8 11093326 14/12/2017 19/12/2017
9 11092475 14/12/2017 19/12/2017
10 11093773 19/12/2017 19/12/2017
# ℹ 11,721 more rows
select 1# A tibble: 11,731 × 3
id_decisao data_decisao txt_decisao
<chr> <chr> <chr>
1 11094999 19/12/2017 <NA>
2 11093733 19/12/2017 <NA>
3 11093677 19/12/2017 <NA>
4 11093270 14/12/2017 "Execução Penal – Comutação de Penas – Decreto n. …
5 11093374 14/12/2017 "Mandado de segurança – Impetração por agente despro…
6 11093320 14/12/2017 "Execução Penal – Apuração de falta grave em procedi…
7 11091506 14/12/2017 "Tráfico de entorpecentes – Agente que traz consigo …
8 11093326 14/12/2017 "Execução Penal – Pedido de livramento condicional d…
9 11092475 14/12/2017 "Tráfico de entorpecentes – Agente que tem em depós…
10 11093773 19/12/2017 <NA>
# ℹ 11,721 more rows
select 2?select em Drop variables ...# A tibble: 11,731 × 7
id_decisao n_processo municipio camara data_decisao data_registro juiz
<chr> <chr> <chr> <chr> <chr> <chr> <chr>
1 11094999 0057003-20.2017… Cosmópol… 3ª Câ… 19/12/2017 19/12/2017 Luiz…
2 11093733 0052762-03.2017… São Paulo 3ª Câ… 19/12/2017 19/12/2017 Luiz…
3 11093677 0055169-79.2017… Ribeirão… 3ª Câ… 19/12/2017 19/12/2017 Luiz…
4 11093270 9000580-82.2017… Araçatuba 8ª Câ… 14/12/2017 19/12/2017 Gras…
5 11093374 0052938-79.2017… São Paulo 8ª Câ… 14/12/2017 19/12/2017 Gras…
6 11093320 9000723-79.2017… Presiden… 8ª Câ… 14/12/2017 19/12/2017 Gras…
7 11091506 0003276-86.2015… Bertioga 8ª Câ… 14/12/2017 19/12/2017 Gras…
8 11093326 9000298-11.2017… Taubaté 8ª Câ… 14/12/2017 19/12/2017 Gras…
9 11092475 0004653-39.2015… Aparecida 8ª Câ… 14/12/2017 19/12/2017 Gras…
10 11093773 2221930-66.2017… Jandira 3ª Câ… 19/12/2017 19/12/2017 Luiz…
# ℹ 11,721 more rows
filter, ou & para “e” e | para “ou”.&.filter em ação# A tibble: 2,446 × 4
n_processo id_decisao municipio juiz
<chr> <chr> <chr> <chr>
1 0052762-03.2017.8.26.0000 11093733 São Paulo Luiz Antonio Cardoso
2 0052938-79.2017.8.26.0000 11093374 São Paulo Grassi Neto
3 2214049-38.2017.8.26.0000 11093604 São Paulo Luiz Antonio Cardoso
4 2227499-48.2017.8.26.0000 11093642 São Paulo Luiz Antonio Cardoso
5 9002384-31.2017.8.26.0050 11093376 São Paulo Grassi Neto
6 0021158-39.2015.8.26.0050 11091508 São Paulo Grassi Neto
7 7005375-26.2015.8.26.0198 11091668 São Paulo Grassi Neto
8 9002039-65.2017.8.26.0050 11094451 São Paulo Grassi Neto
9 2203993-43.2017.8.26.0000 11094449 São Paulo Grassi Neto
10 0099423-21.2016.8.26.0050 11091474 São Paulo Grassi Neto
# ℹ 2,436 more rows
%in%decisoes %>%
select(id_decisao, municipio, data_decisao, juiz) %>%
# municipio igual a campinas ou jaú, OU dia da decisão maior ou igual a 25
filter(municipio %in% c('Campinas', 'Jaú') & day(dmy(data_decisao)) >= 25)# A tibble: 71 × 4
id_decisao municipio data_decisao juiz
<chr> <chr> <chr> <chr>
1 11093018 Jaú 28/11/2017 Ivan Sartori
2 11082822 Campinas 29/11/2017 João Morenghi
3 11082845 Campinas 29/11/2017 João Morenghi
4 11052266 Campinas 30/11/2017 Augusto de Siqueira
5 11052894 Campinas 30/11/2017 Poças Leitão
6 11052213 Campinas 30/11/2017 Poças Leitão
7 11049986 Campinas 29/11/2017 Xavier de Souza
8 11049760 Campinas 30/11/2017 Encinas Manfré
9 11044116 Campinas 30/11/2017 Encinas Manfré
10 11043650 Campinas 30/11/2017 Fernando Torres Garcia
# ℹ 61 more rows
filterdecisoes %>%
select(juiz) %>%
# filtra juízes que têm `Z` ou `z` no nome
filter(str_detect(juiz, regex("z", ignore_case = TRUE))) %>%
# conta e ordena os juizes em ordem decrescente
count(juiz, sort = TRUE) %>%
head(5)# A tibble: 5 × 2
juiz n
<chr> <int>
1 Gilberto Ferreira da Cruz 237
2 Diniz Fernando 198
3 Sérgio Mazina Martins 173
4 Luiz Antonio Cardoso 163
5 Rachid Vaz de Almeida 150
A função str_detect() retorna TRUE se um elemento do vetor de textos é compatível com uma expressão regular. Estudaremos o pacote stringr e as funções str_* em outra aula.
filter 1id_decisao não é NA# A tibble: 11,666 × 9
id_decisao n_processo classe_assunto municipio camara data_decisao
<chr> <chr> <chr> <chr> <chr> <chr>
1 11094999 0057003-20.2017.8.26… Habeas Corpus… Cosmópol… 3ª Câ… 19/12/2017
2 11093733 0052762-03.2017.8.26… Habeas Corpus… São Paulo 3ª Câ… 19/12/2017
3 11093677 0055169-79.2017.8.26… Habeas Corpus… Ribeirão… 3ª Câ… 19/12/2017
4 11093270 9000580-82.2017.8.26… Agravo de Exe… Araçatuba 8ª Câ… 14/12/2017
5 11093374 0052938-79.2017.8.26… Mandado de Se… São Paulo 8ª Câ… 14/12/2017
6 11093320 9000723-79.2017.8.26… Agravo de Exe… Presiden… 8ª Câ… 14/12/2017
7 11091506 0003276-86.2015.8.26… Apelação / Tr… Bertioga 8ª Câ… 14/12/2017
8 11093326 9000298-11.2017.8.26… Agravo de Exe… Taubaté 8ª Câ… 14/12/2017
9 11092475 0004653-39.2015.8.26… Apelação / Tr… Aparecida 8ª Câ… 14/12/2017
10 11093773 2221930-66.2017.8.26… Habeas Corpus… Jandira 3ª Câ… 19/12/2017
# ℹ 11,656 more rows
# ℹ 3 more variables: data_registro <chr>, juiz <chr>, txt_decisao <chr>
filter 2filtre todas as decisões de 2018.
– Dica: função lubridate::year()
# A tibble: 314 × 9
id_decisao n_processo classe_assunto municipio camara data_decisao
<chr> <chr> <chr> <chr> <chr> <chr>
1 11107242 0009617-63.2016.8.26… Apelação / Ro… São Paulo 2ª Câ… 15/01/2018
2 11107425 2227593-93.2017.8.26… Habeas Corpus… Iepê 2ª Câ… 15/01/2018
3 11107492 0076977-24.2016.8.26… Embargos de D… São Paulo 2ª Câ… 15/01/2018
4 11107361 0012191-36.2017.8.26… Agravo de Exe… Campinas 2ª Câ… 15/01/2018
5 11107383 2218460-27.2017.8.26… Habeas Corpus… Sorocaba 2ª Câ… 15/01/2018
6 11107331 0006928-63.2017.8.26… Agravo de Exe… Sorocaba 2ª Câ… 15/01/2018
7 11107651 0000297-54.2017.8.26… Apelação / Tr… Junqueir… 2ª Câ… 15/01/2018
8 11107485 2225548-19.2017.8.26… Habeas Corpus… Nazaré P… 2ª Câ… 15/01/2018
9 11107335 0006934-70.2017.8.26… Agravo de Exe… Sorocaba 2ª Câ… 15/01/2018
10 11107340 0006682-67.2017.8.26… Agravo de Exe… Sorocaba 2ª Câ… 15/01/2018
# ℹ 304 more rows
# ℹ 3 more variables: data_registro <chr>, juiz <chr>, txt_decisao <chr>
mutateAceita várias novas colunas iterativamente.
Novas variáveis devem ter o mesmo length que o nrow do bd original ou 1.
mutate em açãodecisoes %>%
select(n_processo, data_decisao, data_registro) %>%
mutate(tempo = dmy(data_registro) - dmy(data_decisao))# A tibble: 11,731 × 4
n_processo data_decisao data_registro tempo
<chr> <chr> <chr> <drtn>
1 0057003-20.2017.8.26.0000 19/12/2017 19/12/2017 0 days
2 0052762-03.2017.8.26.0000 19/12/2017 19/12/2017 0 days
3 0055169-79.2017.8.26.0000 19/12/2017 19/12/2017 0 days
4 9000580-82.2017.8.26.0032 14/12/2017 19/12/2017 5 days
5 0052938-79.2017.8.26.0000 14/12/2017 19/12/2017 5 days
6 9000723-79.2017.8.26.0482 14/12/2017 19/12/2017 5 days
7 0003276-86.2015.8.26.0075 14/12/2017 19/12/2017 5 days
8 9000298-11.2017.8.26.0625 14/12/2017 19/12/2017 5 days
9 0004653-39.2015.8.26.0028 14/12/2017 19/12/2017 5 days
10 2221930-66.2017.8.26.0000 19/12/2017 19/12/2017 0 days
# ℹ 11,721 more rows
mutate em açãodrogas que vale TRUE se no texto da decisão algo é falado de drogas e FALSE caso contrário. – Dica: str_detectObs.: Considere tanto a palavra ‘droga’ como seus sinônimos, ou algum exemplo de droga e retire os casos em que txt_decisao é vazio
decisoes %>%
filter(!is.na(txt_decisao)) %>% # filtrando quem não é NA
mutate(txt_decisao = tolower(txt_decisao),
droga = str_detect(txt_decisao,
"droga|entorpecente|psicotr[óo]pico|maconha|haxixe|coca[íi]na")
) %>%
dplyr::select(n_processo,droga) # A tibble: 6,933 × 2
n_processo droga
<chr> <lgl>
1 9000580-82.2017.8.26.0032 FALSE
2 0052938-79.2017.8.26.0000 FALSE
3 9000723-79.2017.8.26.0482 FALSE
4 0003276-86.2015.8.26.0075 TRUE
5 9000298-11.2017.8.26.0625 TRUE
6 0004653-39.2015.8.26.0028 TRUE
7 9000788-34.2017.8.26.0269 FALSE
8 9000673-53.2017.8.26.0482 FALSE
9 7005620-87.2017.8.26.0482 FALSE
10 7001988-32.2017.8.26.0198 FALSE
# ℹ 6,923 more rows
summarise1 a partir de uma operação com as variáveis (aplicação de uma função).group_by().n(), n_distinct().summarise Em açãodecisoes %>%
select(n_processo, municipio, data_decisao) %>%
# pega ano da decisão
mutate(ano_julgamento = year(dmy(data_decisao)),
# pega o ano do processo 0057003-20.2017.8.26.0000" -> "2017"
ano_proc = str_sub(n_processo, 12, 15),
# transforma o ano em inteiro
ano_proc = as.numeric(ano_proc),
# calcula o tempo em anos
tempo_anos = ano_julgamento - ano_proc) %>%
group_by(municipio) %>%
summarise(n = n(),
media_anos = mean(tempo_anos,na.rm=T),
min_anos = min(tempo_anos,na.rm=T),
max_anos = max(tempo_anos,na.rm=T)) # A tibble: 315 × 5
municipio n media_anos min_anos max_anos
<chr> <int> <dbl> <dbl> <dbl>
1 Adamantina 17 0.765 0 5
2 Aguaí 19 1.16 0 2
3 Agudos 8 3.25 0 6
4 Altinópolis 7 0.857 0 2
5 Americana 56 1.41 0 9
6 Amparo 9 2.11 0 7
7 Américo Brasiliense 9 1.56 0 3
8 Andradina 41 0.707 0 5
9 Angatuba 4 0.5 0 2
10 Aparecida 20 1.9 0 5
# ℹ 305 more rows
count()A função count(), simplifica um group_by %>% summarise %>% ungroup:
# A tibble: 100 × 3
juiz n prop
<chr> <int> <chr>
1 Gilberto Ferreira da Cruz 237 2.0203%
2 Francisco Orlando 226 1.9265%
3 Diniz Fernando 198 1.6878%
4 Walter da Silva 183 1.5600%
5 De Paula Santos 182 1.5514%
6 Machado de Andrade 182 1.5514%
7 Newton Neves 180 1.5344%
8 Leme Garcia 179 1.5259%
9 Grassi Neto 177 1.5088%
10 Figueiredo Gonçalves 176 1.5003%
# ℹ 90 more rows
mas sem formato %
# A tibble: 100 × 3
juiz n prop
<chr> <int> <dbl>
1 Gilberto Ferreira da Cruz 237 0.0202
2 Francisco Orlando 226 0.0193
3 Diniz Fernando 198 0.0169
4 Walter da Silva 183 0.0156
5 De Paula Santos 182 0.0155
6 Machado de Andrade 182 0.0155
7 Newton Neves 180 0.0153
8 Leme Garcia 179 0.0153
9 Grassi Neto 177 0.0151
10 Figueiredo Gonçalves 176 0.0150
# ℹ 90 more rows
arrangeSimplesmente ordena de acordo com as opções.
Utilizar desc() para ordem decrescente ou o sinal de menos (-).
arrange– Dica: use str_length()
– Lembre-se da função head()
decisoes %>%
filter(!is.na(txt_decisao)) %>%
mutate(tamanho = str_length(txt_decisao)) %>%
group_by(juiz) %>%
summarise(n = n(),
tamanho_mediana = median(tamanho)) %>%
filter(n >= 10) %>%
arrange(desc(tamanho_mediana)) %>%
head()# A tibble: 6 × 3
juiz n tamanho_mediana
<chr> <int> <dbl>
1 Airton Vieira 154 3146.
2 Ely Amioka 81 1847
3 Grassi Neto 141 1675
4 Alcides Malossi Junior 95 1541
5 Cesar Augusto Andrade de Castro 77 1341
6 Juvenal Duarte 101 1320
CURSO DE R